#include "boot_loader.h"
#include "libusb.h"
#include <thread>
#include <chrono>
using namespace std;
BootLoader::BootLoader()
{
	process_ = 0;
	transfer_bytes_ = 0;
	total_bytes_ = 0;
	iap_sta_ = IAP_IDLE;
	timetick_ = 0;	
	int ret = libusb_init(&ctx_);
	if (ret < 0)
	{
		printf("init error");
		throw ;
	}
	libusb_set_debug(ctx_, 3);
	open_flag_ = false;
}
BootLoader::~BootLoader()
{
	libusb_exit(ctx_);
}
void BootLoader::StartDebugThread()
{
	thread debug(&BootLoader::internal_recv_debug,this);
	debug.detach();
}
bool BootLoader::Init()
{
	dev_handle_ = libusb_open_device_with_vid_pid(ctx_, 0x0483, 0x5740);
	if (dev_handle_ == NULL) return false;
	if (libusb_kernel_driver_active(dev_handle_, 0) == 1)
	{
		if (libusb_detach_kernel_driver(dev_handle_, 0) == 0)
		{

		}
	}
	int ret = libusb_claim_interface(dev_handle_, 0);
	if (ret < 0) return false;
	open_flag_ = true;
	return true;
}

std::vector<std::string> BootLoader::USBListDevice()
{
	vector<string> vec;
	string name = "";
	if (open_flag_) return vec;
	if (Init())
	{
		name = "bootloader";
		vec.push_back(name);
	}
	return vec;
}

void BootLoader::Deinit()
{
	libusb_release_interface(dev_handle_, 0);
	//libusb_attach_kernel_driver(dev_handle_, 0);
	libusb_close(dev_handle_);
	open_flag_ = false;
}

void BootLoader::IapUpdate(const char *)
{

}

void BootLoader::IapGet(const char *)
{
}

void BootLoader::internal_recv_debug()
{
	char buf[64] = { 0 };	
	int len = 0; 
	int ret = 0;
	while (1)
	{
		ret = libusb_bulk_transfer(dev_handle_, 2 | 0x80, (uint8_t*)buf, 64, &len, 1000);
		if (ret >= 0)
		{
			buf[len] = 0;
			OutputDebugStringA((char*)buf);
			OutputDebugStringA("\n");
		}
		std::this_thread::sleep_for(chrono::milliseconds(1));

	}
}
